package org.yatr.yatrc;
import java.io.*;
import org.antlr.runtime.*;
import org.antlr.runtime.tree.*;
import org.antlr.stringtemplate.*;

import org.antlr.runtime.debug.*;

class MyCommonTokenStream extends CommonTokenStream{
	public MyCommonTokenStream(Lexer lexer) {
		super(lexer);
	}
	
	boolean myflag=true;

	public Token LT(int k) {
		CommonToken t = (CommonToken)super.LT(k);
		
		int k0, k1, k2;
		if(k==1) {
			k0=-1; k1=1; k2=2;
		} else if(k==-1) {
			k0=-2; k1=-1; k2=1;
		} else {
			k0=k-1; k1=k; k2=k+1;
		}
		
		Token tk0=super.LT(k0), tk1=super.LT(k1), tk2=super.LT(k2);
		
		if(tk0 != null && tk0.getType() == 20 && tk1 != null && tk1.getType()!=21 && myflag)
		{
			System.out.println("in myffff");
			CommonToken tt = new CommonToken(t);//t.getInputStream(), t.getType(), t.getChannel(), t.getCharPositionInLine(), 0);
     
      tt.setType(21);  //';' = 21
      tt.setText(";");

			myflag=false;
			return tt;
		}
		
		myflag=true;
		
		return t;
	}
	
	
}

public class Main {
    boolean printAST=false;
    String inputFile;
    
    boolean procArgs(String[] args) {
        if(args.length != 1) {
            System.err.println("Argument != 1 error.");
            showHelp();
            return false;
        }
        
        for(String arg: args) {
            if(arg.equals("-printAST")) {
                printAST=true;
                return false;
            }
            else if(arg.equals("-h") || arg.equals("--help")) {
                showHelp();
                return false;
            }
            else if(arg.equals("-v") || arg.equals("--version")) {
                showVersion();
                return false;
            }
            else 
                inputFile = arg;
        }
        return true;
    }
    
    void showHelp() {
        System.out.println("Usage: java org.yatr.yatrc.Main file.ttcn");   
    }
    
    void showVersion() {
        showHelp();
    }
    
	public static void main(String[] args) throws Exception {
	    
	    Main in = new Main();
	    in.procArgs(args);
	    
	    if(in.inputFile==null) {
	        return;
	    }
	    
		//CharStream input = new ANTLRFileStream(args[0]);
		//ANTLRInputStream input = new ANTLRInputStream(System.in);
		ANTLRFileStream input = new ANTLRFileStream(in.inputFile);
		
		ttcn3Lexer lex = new ttcn3Lexer(input);
		CommonTokenStream tokens = new CommonTokenStream(lex);
		ttcn3Parser parser = new ttcn3Parser(tokens);
		
		ttcn3Parser.ttcn3File_return r = parser.ttcn3File();
		//ttcn3Parser.expr_return r = parser.expr();
		
		//System.out.println("tree="+((Tree)r.tree).toStringTree());

		if ( parser.getNumberOfSyntaxErrors()>0 || parser.getTtcnErrorCount()>0
		    || lex.getNumberOfSyntaxErrors()>0) {
			System.err.printf("\nLexer Syntax Errors=%d\nParser SyntaxErrors=%d\nSemantic Errors=%d\n",
				lex.getNumberOfSyntaxErrors(), parser.getNumberOfSyntaxErrors(), parser.getTtcnErrorCount());
			// don't tree parse if has errors
			return;
		}
		
		/* for stringtemplate start*/
		FileReader groupFileR  = new FileReader("ttcn3.stg");
		StringTemplateGroup templates = new StringTemplateGroup(groupFileR);
		groupFileR.close();
		/* for stringtemplate end */
		
        CommonTreeNodeStream nodes = new CommonTreeNodeStream((Tree)r.tree);
		nodes.setTokenStream(tokens);
		ttcn3tree walker = new ttcn3tree(nodes);
		
		walker.setTemplateLib(templates);
		
		ttcn3tree.ttcn3File_return r2 = walker.ttcn3File(parser.getSymtblOfModules());
		//ttcn3tree.expr_return r2 = walker.expr();
		
		if(walker.getNumberOfSyntaxErrors() > 0) {
		    System.err.printf("\nTree Parser SyntaxErrors=%d\nSemantic Errors=%d\n",
				lex.getNumberOfSyntaxErrors(), parser.getNumberOfSyntaxErrors(), parser.getTtcnErrorCount());

			return;
		}
		
		//StringTemplate output = (StringTemplate)r2.getTemplate();
		//System.out.println("StringTemplate output:" + output==null?null:output.toString());
		FileWriter outputFile = new FileWriter(in.inputFile+".java");
		//System.out.println("String template:\n"+r2.st);
		outputFile.write(r2.st.toString());
		outputFile.flush();
		outputFile.close();
		
	}
}



/*
Sample file that shows how to connect to AntlrWorks

Remember to change the following to suit your own project
 - XMLGrammarLexer
 - XMLGrammarParser
 - XMLTree

*/
/*
class TreeDebug {

  public static void main(String args[]) throws Exception {
    	CharStream input = new ANTLRFileStream(args[0]);
    	ttcn3Lexer lex = new ttcn3Lexer(input);
			
			// MODIFY: change document to the root rule 
			ParseTreeBuilder builder = new ParseTreeBuilder("ttcn3File"); 

      // create a debug socket proxy to ANTLRWorks
      // MODIFY: change the name of the grammar file
      DebugEventSocketProxy AW = new DebugEventSocketProxy("E:\\softs\\TTCN\\YATR\\ttcn3\\ttcn3tree.g");
      AW.handshake();

			DebugEventHub hub = new DebugEventHub(builder, AW);

      CommonTokenStream tokens = new CommonTokenStream(lex);
      ttcn3Parser parser = new ttcn3Parser(tokens);
			parser.ttcn3File_return root = parser.document();
			
			CommonTreeNodeStream nodes = new CommonTreeNodeStream((Tree)root.tree);
      ttcn3tree walker = new ttcn3tree(nodes, hub);
      try {
					// MODIFY: change to the rule that you want to follow
          walker.ttcn3File();
      } catch (RecognitionException e) {
          e.printStackTrace();
      }
      
  }
}
*/
